home *** CD-ROM | disk | FTP | other *** search
/ Celestin Apprentice 5 / Apprentice-Release5.iso / Source Code / Libraries / Sherlock 2.0 / DevLibSrc / Mac DevLib / mac_via.c < prev   
Text File  |  1995-11-06  |  4KB  |  195 lines

  1.  
  2. /*
  3.  *  mac_via.c, adapted from VIA_TIMER.c.
  4.  *
  5.  *  Copyright (c) 1991 Symantec Corporation.  All rights reserved.
  6.  *
  7.  */
  8.  
  9. #include <LIBlib.h>
  10.  
  11. // From <LoMem.h>:  Warning: can't be used on a Power Mac.
  12. // #include <LoMem.h>
  13.  
  14.     #include <Memory.h>
  15.  
  16.     #define    Declare_LoMem(type, name, address)    type (name) : (address)
  17.     Declare_LoMem(THz, ApplZone, 0x2AA);
  18.     Declare_LoMem(Ptr, VIA, 0x1D4);
  19.     #ifdef THINK_C
  20.         ProcPtr Lvl1DT[] : 0x192;
  21.         ProcPtr Lvl2DT[] : 0x1B2;
  22.     #endif
  23.  
  24. #include <Memory.h>    /* VIA */
  25. #include <stdlib.h>
  26. #include <profile.h>
  27.  
  28. #define vT1C        (512*4)
  29. #define vT1CH        (512*5)
  30. #define vIER        (512*14)
  31.  
  32. struct words { short hi, lo; };
  33. struct bytes { char hi, lo; };
  34.  
  35. /*  tick count  */
  36. static union {
  37.     long            dword;
  38.     struct words    word;
  39. } elapsed;
  40.  
  41. /*  VIA countdown timer #1  */
  42. static union {
  43.     short            word;
  44.     struct bytes    byte;
  45. } timer;
  46.  
  47. static struct {
  48.     ProcPtr            vector;
  49.     char            enable;
  50. } save;
  51.  
  52. static Boolean timer_running, exithook_installed;
  53.  
  54.  
  55. /*
  56.  *  VIA_ticks - return tick count
  57.  *
  58.  *  Each tick represents approximately 1.28 micro-seconds.
  59.  *
  60.  */
  61. void my_start_VIA_timer(int flag);
  62.  
  63. long
  64. VIA_ticks()
  65. {
  66.     long entry_dword = elapsed.dword;
  67.     
  68.     if (!timer_running)
  69.         my_start_VIA_timer(FALSE);
  70.         
  71.     /* Wait for the high byte of the countdown timer to change. */
  72.     do {
  73.         timer.byte.hi = VIA[vT1CH];
  74.         timer.byte.lo = VIA[vT1C];
  75.     } while (timer.byte.hi != VIA[vT1CH]);
  76.     
  77.     /* This sets only the low part.  The high part is set by the rollover. */
  78.     elapsed.word.lo = ~timer.word;
  79.     
  80. #if 0 /* new code: doesn't seem to work at all. */
  81.     if (elapsed.dword < entry_dword) {
  82.         es("VIA_TICKS: adjusting...");
  83.         #if 0
  84.             es("VIA[vIER]: "); ehex(VIA[vIER] & 0xff);
  85.         #endif
  86.         es(" entry elapsed: "); ehex(entry_dword);
  87.         es(" elapsed: "); ehex(elapsed.dword);
  88.         elapsed.word.hi++;
  89.         VIA[vIER] = 0xC0;
  90.         VIA[vT1C] = VIA[vT1CH] = ~0;
  91.         #if 0 /* This always prints as f3, not c0! */
  92.             es("new VIA[vIER]: "); ehex(VIA[vIER] & 0xff);
  93.         #endif
  94.         enl();
  95.     }
  96. #endif
  97.  
  98. #if 0 /* Hangs */
  99.     ecnl(); es("VIA: "); ehex(elapsed.dword); enl();
  100. #endif
  101.     return(elapsed.dword);
  102. }
  103.  
  104. /*
  105.     Compensate for a presumably missed rollover interrup.
  106. */
  107. long my_VIA_rollover(void);
  108. long
  109. my_VIA_rollover(void)
  110. {
  111.     ++elapsed.word.hi;
  112.     VIA[vT1C] = VIA[vT1CH] = ~0;
  113.     return(elapsed.dword);
  114. }
  115.  
  116. /*
  117.  *  start_VIA_timer
  118.  *
  119.  *  It is not necessary to call this routine, as it is automatically
  120.  *  invoked by "VIA_ticks".
  121.  *
  122.  */
  123. void
  124. my_start_VIA_timer(int flag)
  125. {    
  126.         /*  install rollover interrupt  */
  127.  
  128.     /* This does *not* set the elapsed time. */
  129.     VIA[vT1C] = VIA[vT1CH] = ~0;
  130.     
  131.     if (flag == FALSE) {
  132.         save.vector = Lvl1DT[6];
  133.         save.enable = VIA[vIER];
  134.     }
  135.     #if 0
  136.         else {
  137.             ecnl(); es("old vector: "); eptr(save.vector);
  138.             es(" old enable: "); ehex(save.enable); enl();
  139.         }
  140.     #endif
  141.     asm {
  142.         lea        @A5,a0
  143.         move.l    a5,(a0)
  144.         lea        @rollover,a0
  145.         move.l    a0,Lvl1DT[6]
  146.     }
  147.     VIA[vIER] = 0xC0;
  148.  
  149.         /*  arrange for timer to be stopped at exit  */
  150.         
  151.     timer_running = true;
  152.     if (!exithook_installed) {
  153.         _atexit(stop_VIA_timer);
  154.         exithook_installed = true;
  155.     }
  156.     return;
  157.         
  158.         /*  interrupt handler  */
  159.  
  160. rollover:
  161.     /* Save register. */
  162.     asm {
  163.         move.l    a5,-(sp)
  164.         movea.l    @A5,a5
  165.     }
  166.     ++elapsed.word.hi;
  167.     VIA[vT1C] = VIA[vT1CH] = ~0;
  168.     /* Restore register. */
  169.     asm {
  170.         movea.l    (sp)+,a5
  171.         rts
  172. A5:        dc.l    0                ;  store app's A5 here
  173.     }
  174. }
  175.  
  176.  
  177. /*
  178.  *  stop_VIA_timer
  179.  *
  180.  *  It is not necessary to call this routine, as it will be called
  181.  *  automatically at program exit.
  182.  *
  183.  */
  184.  
  185. void
  186. stop_VIA_timer(void)
  187. {
  188.     if (timer_running) {
  189.         if (!(save.enable & 0x40))
  190.             VIA[vIER] = 0x40;
  191.         Lvl1DT[6] = save.vector;
  192.         timer_running = false;
  193.     }
  194. }
  195.